//
//  YXWave.m
//  YXWaveDemo
//
//  Created by Rookie_YX on 16/10/20.
//  Copyright © 2016年 Rookie_YX. All rights reserved.
//

#import "YXWave.h"

@interface YXProxy : NSObject
@property (weak, nonatomic) id executor;
@end

@implementation YXProxy

-(void)callback {
#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Wundeclared-selector"
  
  [_executor performSelector:@selector(wave)];
  
#pragma clang diagnostic pop
}

@end

@interface YXWave ()
/**刷屏器*/
@property (nonatomic, strong) CADisplayLink *timerDisplayLink;
/**真实波浪*/
@property (nonatomic, strong) CAShapeLayer *realShapeLayer;
/** 遮挡层波浪*/
@property (nonatomic, strong) CAShapeLayer *maskShapeLayer;
/**偏移量*/
@property (nonatomic, assign) CGFloat  offset;

@end
@implementation YXWave

#pragma mark - life cycle
- (void)awakeFromNib{
  [super awakeFromNib];
  [self initData];
}

- (instancetype)init
{
  self = [super init];
  if (self) {
    [self initData];
  }
  return self;
}

- (instancetype)initWithFrame:(CGRect)frame
{
  self = [super initWithFrame:frame];
  if (self) {
    [self initData];
  }
  return self;
}



#pragma mark - private method
- (void)initData{
  //初始化
  self.waveSpeed = 0.5;
  self.waveCurvature = 1.5;
  self.waveHeight = 4;
  self.realWaveColor = [UIColor whiteColor];
  self.maskWaveColor = [[UIColor whiteColor] colorWithAlphaComponent:0.4];
  
  [self.layer addSublayer:self.realWaveLayer];
  [self.layer addSublayer:self.maskWaveLayer];
  
}
// 自定义初始化
- (instancetype)initWithFrame:(CGRect)frame  waveSpeed:(CGFloat)speed waveCurvature:(CGFloat)curvature waveHeight:(CGFloat)height realWaveColor:(UIColor *)realColor maskWaveColor:(UIColor *)maskColor {
  self = [super initWithFrame:frame];
  if (self) {
    self.waveSpeed = speed;
    self.waveCurvature = curvature;
    self.waveHeight = height;
    self.realWaveColor = realColor;
    self.maskWaveColor =  maskColor;
    [self.layer addSublayer:self.realShapeLayer];
    [self.layer addSublayer:self.maskShapeLayer];
  }
  return self;
}

- (void)startWaveAnimation{
  YXProxy *proxy = [[YXProxy alloc] init];
  proxy.executor = self;
  self.timerDisplayLink = [CADisplayLink displayLinkWithTarget:proxy selector:@selector(callback)];
  [self.timerDisplayLink addToRunLoop:[NSRunLoop currentRunLoop] forMode:NSRunLoopCommonModes];
}

- (void)stopWaveAnimation{
  
  [self.timerDisplayLink invalidate];
  self.timerDisplayLink = nil;
}

- (void)wave{
  
  self.offset += self.waveSpeed;
  
  CGFloat width = CGRectGetWidth(self.frame);
  CGFloat height = self.waveHeight;
  
  //真实浪
  CGMutablePathRef path = CGPathCreateMutable();
  CGPathMoveToPoint(path, NULL, 0, height);
  CGFloat y = 0.f;
  //遮罩浪
  CGMutablePathRef maskpath = CGPathCreateMutable();
  CGPathMoveToPoint(maskpath, NULL, 0, height);
  CGFloat maskY = 0.f;
  for (CGFloat x = 0.f; x <= width ; x++) {
    // 正弦值
    y = height * sinf(0.01 * self.waveCurvature * x + self.offset * 0.045);
    CGPathAddLineToPoint(path, NULL, x, y);
    maskY = -y;
    CGPathAddLineToPoint(maskpath, NULL, x, maskY);
  }
  
  //变化的中间Y值
  CGFloat centX = self.bounds.size.width/2;
  CGFloat CentY = height * sinf(0.01 * self.waveCurvature *centX  + self.offset * 0.045);
  if (self.waveBlock) {
    self.waveBlock(CentY);
  }
  
  CGPathAddLineToPoint(path, NULL, width, height);
  CGPathAddLineToPoint(path, NULL, 0, height);
  CGPathCloseSubpath(path);
  self.realWaveLayer.path = path;
  self.realWaveLayer.fillColor = self.realWaveColor.CGColor;
  CGPathRelease(path);
  
  CGPathAddLineToPoint(maskpath, NULL, width, height);
  CGPathAddLineToPoint(maskpath, NULL, 0, height);
  CGPathCloseSubpath(maskpath);
  self.maskWaveLayer.path = maskpath;
  self.maskWaveLayer.fillColor = self.maskWaveColor.CGColor;
  CGPathRelease(maskpath);
  
}
#pragma mark - YXProxyDelegate
-(void)callback {
#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Wundeclared-selector"
  [self performSelector:@selector(wave)];
#pragma clang diagnostic pop
}

#pragma mark - getting

- (CAShapeLayer *)realWaveLayer{
  
  if (!_realShapeLayer) {
    _realShapeLayer = [CAShapeLayer layer];
    CGRect frame = [self bounds];
    frame.origin.y = frame.size.height-self.waveHeight;
    frame.size.height = self.waveHeight;
    _realShapeLayer.frame = frame;
    _realShapeLayer.fillColor = self.realWaveColor.CGColor;
    
  }
  return _realShapeLayer;
}

- (CAShapeLayer *)maskWaveLayer{
  
  if (!_maskShapeLayer) {
    _maskShapeLayer = [CAShapeLayer layer];
    CGRect frame = [self bounds];
    frame.origin.y = frame.size.height-self.waveHeight;
    frame.size.height = self.waveHeight;
    _maskShapeLayer.frame = frame;
    _maskShapeLayer.fillColor = self.maskWaveColor.CGColor;
  }
  return _maskShapeLayer;
}

- (void)setWaveHeight:(CGFloat)waveHeight{
  _waveHeight = waveHeight;
  
  CGRect frame = [self bounds];
  frame.origin.y = frame.size.height-self.waveHeight;
  frame.size.height = self.waveHeight;
  _realShapeLayer.frame = frame;
  
  CGRect frame1 = [self bounds];
  frame1.origin.y = frame1.size.height-self.waveHeight;
  frame1.size.height = self.waveHeight;
  _maskShapeLayer.frame = frame1;
  
}
@end

